package com.hz.filesystem.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hz.common.utils.PageUtils;
import com.hz.common.utils.Query;
import com.hz.filesystem.dao.HzFileDao;
import com.hz.filesystem.entity.HzFileEntity;
import com.hz.filesystem.service.HzFileService;
import com.hz.filesystem.web.FoundFileEntity;
import com.hz.utils.CommonUtil;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;


@Service("hzFileService")
public class HzFileServiceImpl extends ServiceImpl<HzFileDao, HzFileEntity> implements HzFileService {

    @Override
    public PageUtils queryPage(Map<String, Object> params) {
        IPage<HzFileEntity> page = this.page(
                new Query<HzFileEntity>().getPage(params),
                new QueryWrapper<HzFileEntity>()
        );

        return new PageUtils(page);
    }

    @Transactional
    @Override
    public boolean createdir(long upperFid, String fileName,long userId,int fileType) {
        HzFileEntity hzFileEntity = new HzFileEntity(upperFid, fileName, userId, fileType);
        if(upperFid == 0){
            List<HzFileEntity> list = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid", userId).eq("file_type",fileType).eq("file_name", fileName).eq("upper_fid",0));
            if(list.size() != 0) return false;
            this.baseMapper.insert(hzFileEntity);
            return true;
        }
        HzFileEntity upperDir;
        if((upperDir = this.baseMapper.selectById(upperFid)) != null && upperDir.getFileType() == 0){
            List<HzFileEntity> list = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid", userId).eq("file_type",fileType).eq("file_name", fileName).eq("upper_fid",upperFid));
            if(list.size() == 0) {
                this.baseMapper.insert(hzFileEntity);
                return true;
            }
        }
        return false;
    }

    @Transactional
    @Override
    public boolean createfile(String fileAddress,long upperFid, String fileName,long userId,int fileType,long fileSize) {

        HzFileEntity hzFileEntity = new HzFileEntity(fileAddress, upperFid, fileName, userId, fileType, CommonUtil.getFileSizeConvert(fileSize));
        if(upperFid == 0){
            List<HzFileEntity> list = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid", userId).eq("file_type",fileType).eq("file_name", fileName).eq("upper_fid",upperFid));
            if(list.size() != 0) return false;
            this.baseMapper.insert(hzFileEntity);
            return true;
        }
        HzFileEntity upperDir = this.baseMapper.selectById(upperFid);
        if(upperDir != null && upperDir.getFileType() == 0) {
            List<HzFileEntity> list = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid", userId).eq("file_type",fileType).eq("file_name", fileName).eq("upper_fid",upperFid));
            if(list.size() == 0) {
                this.baseMapper.insert(hzFileEntity);
                return true;
            }
        }
        return false;
    }

    @Override
    public List<HzFileEntity> queryfilesbyfid(int curPage, int pageSize,long upperFid, long userId) {
        curPage = (curPage-1) * pageSize;
        return this.baseMapper.queryfilesbyfid(curPage, pageSize, upperFid);
    }

    @Override
    public List<FoundFileEntity> queryfilesbyname(String filename, long userId, int fileBelongto) {
        List<FoundFileEntity> files = new ArrayList<>();
        if(fileBelongto == 0){
            //公共资源检索
            List<HzFileEntity> rootFiles = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("file_belongto",fileBelongto).eq("upper_fid",0).notIn("verify_state",0,2).like("file_name","%"+filename+"%"));
            if (rootFiles != null || rootFiles.size() != 0)
                foundFiles(filename, userId, fileBelongto, files, rootFiles);
        }else if(fileBelongto == 1){
            List<HzFileEntity> rootFiles = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid",userId).eq("file_belongto",fileBelongto).eq("upper_fid",0).like("file_name","%"+filename+"%"));
            if (rootFiles != null || rootFiles.size() != 0)
                foundFiles(filename, userId, fileBelongto, files, rootFiles);
        }
        Collections.sort(files, Comparator.comparing(FoundFileEntity::getFileType));
        return files;
    }

    //递归搜索
    private void foundFiles(String filename, long userId, int fileBelongto, List<FoundFileEntity> foundFiles, List<HzFileEntity> files){
        if(fileBelongto == 0){
            for (HzFileEntity file:files){
                FoundFileEntity foundFileEntity = new FoundFileEntity(file);
                foundFiles.add(foundFileEntity);
                if (file.getFileType() == 0){
                    //是目录
                    files = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("file_belongto",fileBelongto).eq("upper_fid",file.getId()).notIn("verify_state",0,2).like("file_name","%"+filename+"%"));
                    if (files != null || files.size() != 0)
                        foundFiles(filename, userId, fileBelongto, foundFiles, files);
                }
            }
        }else if(fileBelongto == 1){
            for (HzFileEntity file:files){
                FoundFileEntity foundFileEntity = new FoundFileEntity(file);
                foundFiles.add(foundFileEntity);
                if (file.getFileType() == 0){
                    //是目录
                    files = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid",userId).eq("file_belongto",fileBelongto).eq("upper_fid",file.getId()).like("file_name","%"+filename+"%"));
                    if (files != null || files.size() != 0)
                        foundFiles(filename, userId, fileBelongto, foundFiles, files);
                }
            }
        }
    }

    @Override
    public List<FoundFileEntity> queryfilesbynameandpca(String filename, long userId, int fileBelongto, int pcatype, Long pcaid) {
        List<FoundFileEntity> files = new ArrayList<>();
        if(fileBelongto == 0){
            //公共资源检索
            //0：省1：市2：区/县
            List<HzFileEntity> rootFiles = null;
            if (pcatype == 0)
                rootFiles = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("file_belongto",fileBelongto).eq("upper_fid",0).eq("pid",pcaid).notIn("verify_state",0,2).like("file_name","%"+filename+"%"));
            else if(pcatype == 1)
                rootFiles = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("file_belongto",fileBelongto).eq("upper_fid",0).eq("cid",pcaid).notIn("verify_state",0,2).like("file_name","%"+filename+"%"));
            else if(pcatype == 2)
                rootFiles = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("file_belongto",fileBelongto).eq("upper_fid",0).eq("aid",pcaid).notIn("verify_state",0,2).like("file_name","%"+filename+"%"));
            if (rootFiles != null || rootFiles.size() != 0)
                foundFiles(filename, userId, fileBelongto, files, rootFiles);
        }else if(fileBelongto == 1){
            List<HzFileEntity> rootFiles = this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("tid",userId).eq("file_belongto",fileBelongto).eq("upper_fid",0).like("file_name","%"+filename+"%"));
            if (rootFiles != null || rootFiles.size() != 0)
                foundFiles(filename, userId, fileBelongto, files, rootFiles);
        }
        Collections.sort(files, Comparator.comparing(FoundFileEntity::getFileType));
        return files;
    }

    @Override
    public Integer querypublicfilesnum() {
        return this.baseMapper.querypublicfilesnum();
    }

    @Override
    public Integer queryfilesnum(long upperFid) {
        return this.baseMapper.queryfilesnum(upperFid);
    }

    @Override
    public JSONObject queryfilesbystate(int verifyState, long userId, int curPage, int pageSize) {
        JSONObject json = new JSONObject();
        json.put("size",pageSize);
        curPage = (curPage -1) * pageSize;
        if(verifyState == 3){
            List<HzFileEntity> hzFiles = this.baseMapper.queryallverifyfiles(userId, curPage, pageSize);
            json.put("record",hzFiles);
            json.put("total",this.baseMapper.queryallverifyfilesnum(userId));
            return json;
        }else if(verifyState == 1 || verifyState == 2 || verifyState == 0) {
            List<HzFileEntity> hzFiles = this.baseMapper.queryfilesbystate(userId, curPage, pageSize, verifyState);
            json.put("record",hzFiles);
            json.put("total",this.baseMapper.queryfilesbystatenum(userId, verifyState));
            return json;
        }
        return null;
    }

    @Override
    public boolean deletebyfid(long fid, long userId) {
        String ids = this.baseMapper.getDeleteFilesIds(fid,userId);
        this.baseMapper.deletebyfids(ids);
        return true;
    }


    @Transactional
    @Override
    public boolean deletefilesbyids(List<String> ids, long userId) {
        for (String id1:ids) {
            long id = Long.parseLong(id1);
            HzFileEntity hzFileEntity = this.baseMapper.selectById(id);
            if(hzFileEntity != null && hzFileEntity.getFileType() == 0) {
                String idstr = this.baseMapper.getDeleteFilesIds(id, userId);
                this.baseMapper.deletebyfids(idstr);
            }else if(hzFileEntity != null && hzFileEntity.getFileType() == 1)
                this.baseMapper.deleteById(id);
        }
        return true;
    }

    @Override
    public boolean addfiledowncount(long fid) {
        this.baseMapper.addfiledowncount(fid);
        return true;
    }

//公共资源

    @Override
    public List<HzFileEntity> querypublicfilesbyfid(long upperFid, long userId) {
        return this.baseMapper.querypublicfilesbyfid(upperFid, userId);
    }

    @Override
    public List<HzFileEntity> querypublicfilesbydowncount(int curPage,int pageSize) {
        curPage = pageSize * (curPage-1);
        return this.baseMapper.querypublicfilesbydowncount(curPage, pageSize);
    }

    @Override
    public List<HzFileEntity> querypublicfilesbyfidpca(long upperFid, long userId, Integer pcatype, Long pcaid) {
        //0：省1：市2：区/县
        if (pcatype == 0)
            return this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("pid",pcaid).eq("file_type",1).eq("file_belongto",0).orderByDesc("file_loaddown_count"));
        else if(pcatype == 1)
            return this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("cid",pcaid).eq("file_type",1).eq("file_belongto",0).orderByDesc("file_loaddown_count"));
        else if(pcatype == 2)
            return this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("aid",pcaid).eq("file_type",1).eq("file_belongto",0).orderByDesc("file_loaddown_count"));
        return null;
    }

    @Override
    public boolean changefiletodir(long fid, long did, long userId) {
        HzFileEntity hzFileEntity = new HzFileEntity();
        hzFileEntity.setUpperFid(did);
        hzFileEntity.setUpdateTime(new Date());
        this.baseMapper.update(hzFileEntity,new QueryWrapper<HzFileEntity>().eq("id",fid).eq("tid",userId));
        return true;
    }

    @Override
    public List<HzFileEntity> getalldirsbyfid(long upperFid, long userId) {
        return this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("upper_fid",upperFid).eq("file_belongto",1).eq("file_type",0).eq("tid",userId));
    }

    @Override
    public List<HzFileEntity> getalldirsbyfidtomove(long upperFid, long userId, long mfid) {
        return this.baseMapper.selectList(new QueryWrapper<HzFileEntity>().eq("upper_fid",upperFid).eq("file_belongto",1).eq("file_type",0).eq("tid",userId).notIn("id",mfid));
    }

}